import java.security.InvalidParameterException;
import wallet.core.java.GenericPhantomReference;

<%  less = entity.static_methods.detect{ |i| i.name == 'Less' } -%>
<%  equal = entity.static_methods.detect{ |i| i.name == 'Equal' } -%>
<%= entity.comment %>
<%  if !less.nil? && !equal.nil? -%>
public final class <%= entity.name %> implements Comparable<<%= entity.name %>> {
<%  else -%>
public final class <%= entity.name %> {
<%  end -%>
    private long nativeHandle;

<%  unless entity.static_methods.detect{ |m| m.name == 'Create' && m.parameters.empty? } -%>
    private <%= entity.name %>() {
        nativeHandle = 0;
    }

<%  end -%>
    static <%= entity.name %> createFromNative(long nativeHandle) {
        <%= entity.name %> instance = new <%= entity.name %>();
        instance.nativeHandle = nativeHandle;
<%  unless entity.methods.select{ |x| x.name == "Delete" }.empty? -%>
        GenericPhantomReference.register(instance, nativeHandle, <%= entity.name %>::nativeDelete);
<%  end -%>
        return instance;
    }
<%# Constructor declarations -%>
<% entity.static_methods.each do |method| -%>
<%   next unless method.name.start_with?('Create') -%>
<%= method.comment_with_indent %>
    static native long native<%= method.name %>(<%= JavaHelper.parameters(method.parameters) %>);
<% end -%>
<%# Destructor declarations -%>
<% entity.methods.each do |method| -%>
<%   next unless method.name.start_with?('Delete') -%>
    static native void native<%= method.name %>(long handle);
<% end -%>
<%# Static property declarations -%>
<%  entity.static_properties.each do |property| -%>
<%= property.comment_with_indent %>
<%    if should_return_data(property) -%>
    public static native byte[] <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters) %>);
<%    elsif should_return_string(property) -%>
    public static native String <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters) %>);
<%    else -%>
    public static native <%= JavaHelper.type(property.return_type) %> <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters) %>);
<%    end -%>
<% end -%>
<%# Static method declarations -%>
<%  entity.static_methods.each do |method| -%>
<%    next if method.name.start_with?('Create') -%>
<%= method.comment_with_indent %>
<%    if should_return_data(method) -%>
    public static native byte[] <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters) %>);
<%    elsif should_return_string(method) -%>
    public static native String <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters) %>);
<%    else -%>
    public static native <%= JavaHelper.type(method.return_type) %> <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters) %>);
<%    end -%>
<%  end -%>
<%# Property declarations -%>
<%  entity.properties.each do |property| -%>
<%= property.comment_with_indent %>
<%    if should_return_data(property) -%>
    public native byte[] <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters.drop(1)) %>);
<%    elsif should_return_string(property) -%>
    public native String <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters.drop(1)) %>);
<%    else -%>
    public native <%= JavaHelper.type(property.return_type) %> <%= JavaHelper.format_name(property.name) %>(<%= JavaHelper.parameters(property.parameters.drop(1)) %>);
<%    end -%>
<%  end -%>
<%# Method declarations -%>
<%  entity.methods.each do |method| -%>
<%    next if method.name.start_with?('Delete') -%>
<%= method.comment_with_indent %>
<%    if should_return_data(method) -%>
    public native byte[] <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters.drop(1)) %>);
<%    elsif should_return_string(method) -%>
    public native String <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters.drop(1)) %>);
<%    else -%>
    public native <%= JavaHelper.type(method.return_type) %> <%= JavaHelper.format_name(method.name) %>(<%= JavaHelper.parameters(method.parameters.drop(1)) %>);
<%    end -%>
<%  end -%>
<%  if !less.nil? && !equal.nil? -%>
<%    compareMethod = JNIHelper.compareMethod(entity) -%>
    public native <%= JavaHelper.type(compareMethod.return_type) %> <%= JavaHelper.format_name(compareMethod.name) %>(<%= JavaHelper.parameters(compareMethod.parameters.drop(1)) %>);
<%  end -%>
<%# Constructors -%>
<%- entity.static_methods.each do |method| -%>
    <%- next unless method.name.start_with?('Create') -%>
<%= method.comment_with_indent %>
    public <%= entity.name %>(<%= JavaHelper.parameters(method.parameters) %>) {
        nativeHandle = native<%= method.name %>(<%= JavaHelper.arguments(method.parameters) %>);
        if (nativeHandle == 0) {
            throw new InvalidParameterException();
        }

        GenericPhantomReference.register(this, nativeHandle, <%= entity.name %>::nativeDelete);
    }

<%- end -%>
}
